﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Text;

namespace CoolpadContactConverter
{
    class ReadSourceState : IState
    {
        const int START_LOCATION = 4;
        const int BLOCK_LENGTH = 3596;
        const int NAME_TO_PHONE = 4;
        const int NAME_LENGTH = 136;
        const int PHONE_LENGTH = 66;
        const int MAX_PHONE_COUNT = 4;

        public IState Do()
        {
            Console.ForegroundColor = ConsoleColor.Yellow;
            Console.Write("\r\n指定酷派导出的联系人的TBL文件。");
            Console.ForegroundColor = ConsoleColor.DarkGray;
            Console.WriteLine("例如E:\\linkman.tbl。");

            try
            {
                Console.ForegroundColor = ConsoleColor.White;
                ((SaveToDestnationState)Program.SaveToDestnationState).Contacts = ReadCoolpadLinkmanTblFile(Console.ReadLine().Trim(new char[] { '\"', ' ' }));
            }
            catch (IOException e)
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine(e.Message);
                return this;
            }
            return Program.SaveToDestnationState;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        /// <exception cref="IOException"></exception>
        private Contact[] ReadCoolpadLinkmanTblFile(string path)
        {
            byte[] bs = new byte[BLOCK_LENGTH];
            Contact[] result;
            using (FileStream fs = new FileStream(path, FileMode.Open))
            {

                LeapOverBeginning(fs, START_LOCATION);
                result = ReadBlocks(fs, bs);
            }
            return result;
        }

        private Contact[] ReadBlocks(FileStream fs, byte[] bs)
        {
            List<Contact> list = new List<Contact>(50);
            while (fs.Read(bs, 0, BLOCK_LENGTH) > 0)
            {
                int index = 0;
                string name = new string(Encoding.Unicode.GetChars(bs, index, NAME_LENGTH)).Trim('\0');
                index += NAME_LENGTH + NAME_TO_PHONE;

                string[] phones = new string[MAX_PHONE_COUNT];
                for (int i = 0; i < MAX_PHONE_COUNT; i++)
                {
                    phones[i] = new string(Encoding.Unicode.GetChars(bs, index, PHONE_LENGTH)).Trim('\0');
                    index += PHONE_LENGTH;
                }
                list.Add(new Contact(name, phones));
            }
            return list.ToArray();
        }

        /// <summary>
        /// 跳过开头
        /// </summary>
        /// <param name="fs"></param>
        /// <param name="length"></param>
        private void LeapOverBeginning(FileStream fs, int length)
        { fs.Seek(length, SeekOrigin.Begin); }
    }
}
